/*

   Licensed to the Apache Software Foundation (ASF) under one or more
   contributor license agreements.  See the NOTICE file distributed with
   this work for additional information regarding copyright ownership.
   The ASF licenses this file to You under the Apache License, Version 2.0
   (the "License"); you may not use this file except in compliance with
   the License.  You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.

 */
//package org.apache.batik.parser;

//import java.io.IOException;

/**
 * This code was adapted to Objective C from the Apache Java code of the same name.
 * October 17, 2009
 * @author <a href="mailto:chuck@kollar.com">Charles Kollar</a>
 */


/**
 * This interface must be implemented and then registred as the
 * handler of a <code>PathParser</code> instance in order to be
 * notified of parsing events.
 *
 * @author <a href="mailto:stephane@hillion.org">Stephane Hillion</a>
 * @version $Id: PathHandler.java 475685 2006-11-16 11:16:05Z cam $
 */

#import "common.h"

@protocol PathHandler

@required

/**
 * Invoked when the path starts.
 * @exception ParseException if an error occured while processing the path
 */
-(void) startPath; // throws ParseException ;
    
/**
 * Invoked when the path ends.
 * @exception ParseException if an error occured while processing the path
 */
-(void) endPath; // throws ParseException ;

/**
 * Invoked when a relative moveto command has been parsed.
 * <p>Command : <b>m</b>
 * @param x the relative x coordinate for the end point
 * @param y the relative y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) movetoRelX:(float)x Y:(float)y; // throws ParseException;

/**
 * Invoked when an absolute moveto command has been parsed.
 * <p>Command : <b>M</b>
 * @param x the absolute x coordinate for the end point
 * @param y the absolute y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) movetoAbsX:(float) x Y:(float) y; // throws ParseException;

/**
 * Invoked when a closepath has been parsed.
 * <p>Command : <b>z</b> | <b>Z</b>
 * @exception ParseException if an error occured while processing the path
 */
-(void) closePath; // throws ParseException;

/**
 * Invoked when a relative line command has been parsed.
 * <p>Command : <b>l</b>
 * @param x the relative x coordinates for the end point
 * @param y the relative y coordinates for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) linetoRelX:(float)x Y:(float)y; // throws ParseException;
    
/**
 * Invoked when an absolute line command has been parsed.
 * <p>Command : <b>L</b>
 * @param x the absolute x coordinate for the end point
 * @param y the absolute y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) linetoAbsX:(float)x Y:(float)y; // throws ParseException;

/**
 * Invoked when an horizontal relative line command has been parsed.
 * <p>Command : <b>h</b>
 * @param x the relative X coordinate of the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) linetoHorizontalRelX:(float)x; // throws ParseException;

/**
 * Invoked when an horizontal absolute line command has been parsed.
 * <p>Command : <b>H</b>
 * @param x the absolute X coordinate of the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) linetoHorizontalAbsX:(float)x; // throws ParseException;
    
/**
 * Invoked when a vertical relative line command has been parsed.
 * <p>Command : <b>v</b>
 * @param y the relative Y coordinate of the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) linetoVerticalRelY:(float)y; // throws ParseException;

/**
 * Invoked when a vertical absolute line command has been parsed.
 * <p>Command : <b>V</b>
 * @param y the absolute Y coordinate of the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) linetoVerticalAbsY:(float)y; // throws ParseException;

/**
 * Invoked when a relative cubic bezier curve command has been parsed.
 * <p>Command : <b>c</b>
 * @param x1 the relative x coordinate for the first control point
 * @param y1 the relative y coordinate for the first control point
 * @param x2 the relative x coordinate for the second control point
 * @param y2 the relative y coordinate for the second control point
 * @param x the relative x coordinate for the end point
 * @param y the relative y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoCubicRelX1:(float)x1 Y1:(float)y1 X2:(float)x2 Y2:(float)y2 X:(float)x Y:(float)y; // throws ParseException;
    
/**
 * Invoked when an absolute cubic bezier curve command has been parsed.
 * <p>Command : <b>C</b>
 * @param x1 the absolute x coordinate for the first control point
 * @param y1 the absolute y coordinate for the first control point
 * @param x2 the absolute x coordinate for the second control point
 * @param y2 the absolute y coordinate for the second control point
 * @param x the absolute x coordinate for the end point
 * @param y the absolute y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoCubicAbsX1:(float)x1 Y1:(float)y1 X2:(float)x2 Y2:(float)y2 X:(float)x Y:(float)y; // throws ParseException;

/**
 * Invoked when a relative smooth cubic bezier curve command has
 * been parsed. The first control point is assumed to be the
 * reflection of the second control point on the previous command
 * relative to the current point.
 * <p>Command : <b>s</b>
 * @param x2 the relative x coordinate for the second control point
 * @param y2 the relative y coordinate for the second control point
 * @param x the relative x coordinate for the end point
 * @param y the relative y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoCubicSmoothRelX2:(float)x2 Y2:(float)y2 X:(float)x Y:(float) y; // throws ParseException;
    
/**
 * Invoked when an absolute smooth cubic bezier curve command has
 * been parsed. The first control point is assumed to be the
 * reflection of the second control point on the previous command
 * relative to the current point.
 * <p>Command : <b>S</b>
 * @param x2 the absolute x coordinate for the second control point
 * @param y2 the absolute y coordinate for the second control point
 * @param x the absolute x coordinate for the end point
 * @param y the absolute y coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoCubicSmoothAbsX2:(float)x2 Y2:(float)y2 X:(float)x Y:(float)y; // throws ParseException;

/**
 * Invoked when a relative quadratic bezier curve command has been parsed.
 * <p>Command : <b>q</b>
 * @param x1 the relative x coordinate for the control point
 * @param y1 the relative y coordinate for the control point
 * @param x the relative x coordinate for the end point
 * @param y the relative x coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoQuadraticRelX1:(float)x1 Y1:(float)y1 X:(float)x Y:(float)y; // throws ParseException;
    
/**
 * Invoked when an absolute quadratic bezier curve command has been parsed.
 * <p>Command : <b>Q</b>
 * @param x1 the absolute x coordinate for the control point
 * @param y1 the absolute y coordinate for the control point
 * @param x the absolute x coordinate for the end point
 * @param y the absolute x coordinate for the end point
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoQuadraticAbsX1:(float)x1 Y1:(float)y1 X:(float)x Y:(float) y; // throws ParseException;

/**
 * Invoked when a relative smooth quadratic bezier curve command
 * has been parsed. The control point is assumed to be the
 * reflection of the control point on the previous command
 * relative to the current point.
 * <p>Command : <b>t</b>
 * @param x the relative x coordinate for the end point 
 * @param y the relative y coordinate for the end point 
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoQuadraticSmoothRelX:(float)x Y:(float)y; // throws ParseException;
    
/**
 * Invoked when an absolute smooth quadratic bezier curve command
 * has been parsed. The control point is assumed to be the
 * reflection of the control point on the previous command
 * relative to the current point.
 * <p>Command : <b>T</b>
 * @param x the absolute x coordinate for the end point 
 * @param y the absolute y coordinate for the end point 
 * @exception ParseException if an error occured while processing the path
 */
-(void) curvetoQuadraticSmoothAbsX:(float)x Y:(float)y; // throws ParseException;

/**
 * Invoked when a relative elliptical arc command has been parsed. 
 * <p>Command : <b>a</b>
 * @param rx the X axis radius for the ellipse
 * @param ry the Y axis radius for the ellipse 
 * @param xAxisRotation the rotation angle in degrees for the ellipse's
 *                      X-axis relative to the X-axis
 * @param largeArcFlag the value of the large-arc-flag 
 * @param sweepFlag the value of the sweep-flag 
 * @param x the relative x coordinate for the end point 
 * @param y the relative y coordinate for the end point 
 * @exception ParseException if an error occured while processing the path
 */
-(void) arcRelRx:(float)rx Ry:(float)ry XAxisRotation:(float)xar LargeArcFlag:(BOOL)laf SweepFlag:(BOOL)sw X:(float)x Y:(float)y; // throws ParseException;
    
/**
 * Invoked when an absolute elliptical arc command has been parsed.
 * <p>Command : <b>A</b>
 * @param rx the X axis radius for the ellipse
 * @param ry the Y axis radius for the ellipse 
 * @param xAxisRotation the rotation angle in degrees for the ellipse's
 *                      X-axis relative to the X-axis
 * @param largeArcFlag the value of the large-arc-flag 
 * @param sweepFlag the value of the sweep-flag 
 * @param x the absolute x coordinate for the end point 
 * @param y the absolute y coordinate for the end point 
 * @exception ParseException if an error occured while processing the path
 */
-(void) arcAbsRx:(float)rx Ry:(float)ry XAxisRotation:(float)xar LargeArcFlag:(BOOL)laf SweepFlag:(BOOL)sw X:(float)x Y:(float)y; // throws ParseException;

@end


/**
 * This class implements an event-based parser for the SVG path's d
 * attribute values.
 *
 * @author <a href="mailto:stephane@hillion.org">Stephane Hillion</a>
 * @version $Id: PathParser.java 502167 2007-02-01 09:26:51Z dvholten $
 */

@interface PathParser : NSObject {
    
@protected
    // The path handler used to report parse events.
    // remember that id == NSObject *
    id<PathHandler> pathHandler;
    
@private
    // path string broken up into tokens
    NSArray *stringTokens;
    // Current index into token array
    int tokenI;
    // The current token string
    NSString *current;
    // Should we be looking for signs of a new path?
    BOOL mWasParsed;
}

@property (readwrite,assign) id<PathHandler> pathHandler;
@property (readwrite,assign) NSArray *stringTokens;
@property (readwrite,assign) int tokenI;
@property (readwrite,assign) NSString *current;
@property (readwrite,assign) BOOL mWasParsed;

-(id)initWithPathHandler:(id<PathHandler>)ph data:(NSString *)dat;
-(void)doParse;
-(void)dealloc;

// code calling ''doParse'' should @catch the following exceptions
#define EXCEPTION_RMTTA                 @"Requesting More Tokens Than Available"
#define EXCEPTION_EASPC                 @"Expected a SVG Path Command"
#define EXCEPTION_EOTE                  @"End Of Tokens Expected"
#define EXCEPTION_EOF                   @"Expected One Floats"
#define EXCEPTION_ETCSF                 @"Expected Two Comma Separated Floats"
-(void) doParse;

@end


